package com.kavin.playbutton;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.RectF;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.util.AttributeSet;
import android.util.TypedValue;
import android.view.View;
import android.view.View.OnClickListener;


/**
 * 仿微信视频播放按钮
 *
 * @author Vitor kavin_tian
 */
public class PlayButton extends View implements OnClickListener {
    /**
     * 默认最大角度
     */
    private static final int DEFAULT_MAX_ANGLE = 360;
    /**
     * 默认最大的进度
     */
    private static final int DEFAULT_MAX_PROGRESS = 100;
    /**
     * 描边宽度
     */
    private int mStrokeWidth;
    /**
     * 外圆环半径
     */
    private float mOutRadius;
    /**
     * 内圆半径
     */
    private float mInnerRiadius;
    /**
     * 控件的宽度
     */
    private float mWidth;
    /**
     * 控件的高度
     */
    private float mHeight;
    /**
     * 描边的画笔
     */
    private Paint mStrokePaint;
    /**
     * 实心画笔
     */
    private Paint mFillPaint;
    /**
     * 进度圆的
     */
    private RectF mProgressOval;
    /**
     * 最大进度
     */
    private int mMax = DEFAULT_MAX_PROGRESS;
    /**
     * 当前进度
     */
    private int mProgress;
    /**
     * 三角形的路径
     */
    private Path mTriangle;
    private volatile ProgressState mCurrentState = ProgressState.PRE_START;
//    private volatile ProgressState mCurrentState = ProgressState.RUNNING;

    public PlayButton(Context context) {
        this(context, null);
    }

    public PlayButton(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public PlayButton(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        initParams();
        initAttribute(context, attrs, defStyle);
    }

    private void initParams() {
        mStrokeWidth = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, 1, getResources().getDisplayMetrics());

        //初始化描边的笔
        mStrokePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mStrokePaint.setStyle(Paint.Style.STROKE);
//        mStrokePaint.setStrokeWidth(mStrokeWidth);
//        mStrokePaint.setColor(Color.WHITE);

        //初始化画实心的笔
        mFillPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mFillPaint.setStyle(Paint.Style.FILL);
//        mFillPaint.setColor(Color.WHITE);

        setOnClickListener(this);
    }

    private void initAttribute(Context context, AttributeSet attrs, int defStyle) {
        //TODO 增加自定义属性，解析应用自定义属性

        final TypedArray attributes = getContext().obtainStyledAttributes(attrs, R.styleable.PlayButton);
        mStrokeWidth = attributes.getDimensionPixelOffset(R.styleable.PlayButton_lineWidth, mStrokeWidth);
        int lineColor = attributes.getColor(R.styleable.PlayButton_lineColor, Color.WHITE);
        int progressColor = attributes.getColor(R.styleable.PlayButton_progressColor, Color.WHITE);

        mStrokePaint.setStrokeWidth(mStrokeWidth);
        mStrokePaint.setColor(lineColor);
        mFillPaint.setColor(progressColor);
    }

    @Override
    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
        super.onSizeChanged(w, h, oldw, oldh);
        mWidth = w;
        mHeight = h;

        //计算外环的半径 得到控件宽高的最小值作为圆的半径，还要减去掉描边的宽度的一半(描边宽度是以坐标点两边扩散,线的中心点是坐标点)
        mOutRadius = (Math.min(w, h)) / 2f - mStrokeWidth / 2;
        //计算进度圆的半径，外圆减去描边宽度
        mInnerRiadius = mOutRadius - mStrokeWidth / 2;
//        mInnerRiadius = mOutRadius;
        //确定进度圆的范围
        mProgressOval = new RectF(mWidth / 2f - mInnerRiadius, mHeight / 2f - mInnerRiadius,
                mWidth / 2f + mInnerRiadius, mHeight / 2f + mInnerRiadius);

        float triangleHeight = mOutRadius / 3;
        //用三个点来确定三角形的位置，这里以外圆环直径的1/3作为三角形的水平方向的高度，
        //水平方向向右做了 1/2高度的偏移，让三角形中心与圆的中心重叠（从视觉上来说是中心了，从科学的角度来讲这里应该不是中心，博主数学基础不扎实。。）
        mTriangle = new Path();
        mTriangle.moveTo(w / 2 - triangleHeight / 2, w / 2 - triangleHeight);
        mTriangle.lineTo(w / 2 + triangleHeight + triangleHeight / 2, h / 2);
        mTriangle.lineTo(w / 2 - triangleHeight / 2, w / 2 + triangleHeight);
        mTriangle.close();
        //等边三角形
//        mRantange = new Path();
//        float halfOfRantangeHeight = (float) (Math.sqrt(1f/27*Math.pow(mOutRadius*2,2)));
//        Log.e("xxx","mOutRadius/3="+mOutRadius/3+" ,halfOfRantangeHeight="+halfOfRantangeHeight);
//        mRantange.moveTo(w/2-mOutRadius/6,h/2-halfOfRantangeHeight);
//        mRantange.lineTo(w/2+mOutRadius/3+mOutRadius/6,h/2);
//        mRantange.lineTo(w/2-mOutRadius/6,h/2+halfOfRantangeHeight);
//        mRantange.close();

    }

    @Override
    protected void onDraw(Canvas canvas) {
        //绘制外圆环
        canvas.drawCircle(mWidth / 2f, mHeight / 2f, mOutRadius, mStrokePaint);
        if (mCurrentState == ProgressState.RUNNING) {//运行状态，绘制进度圆
            canvas.drawArc(mProgressOval, -90, (mProgress * 1f / mMax * DEFAULT_MAX_ANGLE), true, mFillPaint);
        } else {//非运行状态画三角形
            canvas.drawPath(mTriangle, mStrokePaint);
        }
    }

    @Override
    public void onClick(View v) {

        switch (mCurrentState) {
            case PRE_START:
            case COMPLETELY:
                startAutoLoad();
                break;
            case RUNNING:
                stopAutoLoad();
                break;
        }


        /*switch (mCurrentState) {
            case PRE_START:
                if (listener != null) {
                    listener.onStart();
                }
                mCurrentState = ProgressState.RUNNING;
                break;
            case RUNNING:
                if (listener != null) {
                    listener.onPause(mProgress * 100 / mMax);
                }
                mCurrentState = ProgressState.PAUSE;
                invalidate();
                break;
            case PAUSE:
                if (listener != null) {
                    listener.onStart();
                }
                mCurrentState = ProgressState.RUNNING;
                invalidate();
                break;
            case COMPLETELY:
                if (listener != null) {
                    listener.onCompletedClick();
                }
                break;
        }*/
    }

    Handler handler = new Handler(Looper.getMainLooper()) {
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);

            if (msg.what == 100) {
                startAutoLoad();
            }

        }
    };

    public void startAutoLoad() {
        mCurrentState = ProgressState.RUNNING;

        handler.sendEmptyMessageDelayed(100, speed);

        setProgress(mProgress);
        mProgress++;
        if (mProgress >= mMax) {
            mProgress = 0;
            mCurrentState = ProgressState.COMPLETELY;
            invalidate();
        }

    }

    public void stopAutoLoad() {
        handler.removeCallbacksAndMessages(null);
        mCurrentState = ProgressState.COMPLETELY;
        invalidate();
    }


    public int speed = 20;

    public void setSpeed(int speed) {
        this.speed = 100 - speed;
    }


    private OnProgressClickListener listener;

    /**
     * 设置最大值
     *
     * @param max 最大值
     */
    public void setMax(int max) {
        mMax = max;
    }

    /**
     * 设置当前进度
     *
     * @param progress 当前进度
     */
    public void setProgress(int progress) {
        mProgress = progress;
        if (mCurrentState != ProgressState.RUNNING) {
            mCurrentState = ProgressState.RUNNING;
        }
       /* if (mProgress >= mMax) {
            mCurrentState = ProgressState.COMPLETELY;
            if (listener != null) {//进度圆完成回调
                listener.onCompletely();
            }
        }*/
        invalidate();
    }

    public void reset() {
        mProgress = 0;
        mCurrentState = ProgressState.PRE_START;
        invalidate();
    }

    /**
     * 设置监听事件
     *
     * @param l 监听器
     */
    public void setOnProgressClickListener(OnProgressClickListener l) {
        this.listener = l;
    }

    public void setState(ProgressState state) {
        mCurrentState = state;
    }

    /**
     * 这里提供了四个回调方法，比较多，可能只用到其中几个，
     * 所以采用了抽象类来实现，除了必要的开始操作以外，
     * 其他的操作用户需要哪个方法自己复写就行了。
     */
    public static abstract class OnProgressClickListener {
        /**
         * 开始
         */
        public abstract void onStart();

        /**
         * 暂停
         */
        public void onPause(int percent) {
        }

        ;

        /**
         * 结束
         */
        public void onCompletely() {
        }

        ;

        /**
         * 完成后点击
         */
        public void onCompletedClick() {
        }

        ;
    }

    /**
     * 控件状态
     */
    public enum ProgressState {
        /**
         * 开始之前
         */
        PRE_START,
        /**
         * 运行
         */
        RUNNING,
        /**
         * 暂停
         */
        PAUSE,
        /**
         * 完成
         */
        COMPLETELY;
    }

}